home *** CD-ROM | disk | FTP | other *** search
/ Personal Computer World 2009 February / PCWFEB09.iso / Software / Linux / SLAX 6.0.8 / slax-6.0.8.iso / slax / base / 006-devel.lzm / usr / include / libkmid / track.h < prev    next >
Encoding:
C/C++ Source or Header  |  2007-10-08  |  5.6 KB  |  238 lines

  1. /*  track.h  - class track, which has a midi file track and its events
  2.     This file is part of LibKMid 0.9.5
  3.     Copyright (C) 1997,98,99,2000  Antonio Larrosa Jimenez
  4.     LibKMid's homepage : http://www.arrakis.es/~rlarrosa/libkmid.html
  5.  
  6.     This library is free software; you can redistribute it and/or
  7.     modify it under the terms of the GNU Library General Public
  8.     License as published by the Free Software Foundation; either
  9.     version 2 of the License, or (at your option) any later version.
  10.  
  11.     This library is distributed in the hope that it will be useful,
  12.     but WITHOUT ANY WARRANTY; without even the implied warranty of
  13.     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  14.     Library General Public License for more details.
  15.  
  16.     You should have received a copy of the GNU Library General Public License
  17.     along with this library; see the file COPYING.LIB.  If not, write to
  18.     the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
  19.     Boston, MA 02110-1301, USA.                                                  
  20.  
  21.     Send comments and bug fixes to Antonio Larrosa <larrosa@kde.org>
  22.  
  23. ***************************************************************************/
  24. #ifndef _TRACK_H
  25. #define _TRACK_H
  26.  
  27. #include <stdio.h>
  28. #include <libkmid/dattypes.h>
  29.  
  30. /**
  31.  * An structure that represents a MIDI event.
  32.  *
  33.  * @short Represents a MIDI event
  34.  * @version 0.9.5 17/01/2000
  35.  * @author Antonio Larrosa Jimenez <larrosa@kde.org>
  36.  */ 
  37. struct MidiEvent
  38. {
  39.   /**
  40.    * MIDI Command
  41.    * 
  42.    * Caution, if a command doesn't use a variable, it may contain garbage.
  43.    */
  44.   uchar    command;
  45.  
  46.   /**
  47.    * Channel
  48.    */
  49.   uchar   chn;
  50.  
  51.   /**
  52.    * Note
  53.    */
  54.   uchar   note;
  55.  
  56.   /**
  57.    * Velocity
  58.    */
  59.   uchar   vel;
  60.  
  61.   /**
  62.    * Patch (if command was a change patch command)
  63.    */
  64.   uchar   patch;
  65.  
  66.   /**
  67.    * Patch (if command was a controller command)
  68.    */
  69.   uchar   ctl;
  70.  
  71.   /**
  72.    * Data 1
  73.    */
  74.   uchar   d1;
  75.  
  76.   /**
  77.    * Data 2
  78.    */
  79.   uchar   d2;
  80.  
  81.   /**
  82.    * Data 3
  83.    */
  84.   uchar   d3;
  85.  
  86.   /**
  87.    * Data 4
  88.    */
  89.   uchar   d4;
  90.  
  91.   /**
  92.    * Data 5
  93.    */
  94.   uchar   d5;
  95.  
  96.   /**
  97.    * Data 6
  98.    */
  99.   uchar   d6;
  100.  
  101.   /**
  102.    * Length of the generic data variable
  103.    */
  104.   ulong    length;
  105.  
  106.   /**
  107.    * The data for commands like text, sysex, etc.
  108.    */
  109.   uchar  *data;
  110.  
  111. };
  112.  
  113. /**
  114.  * Stores a MIDI track. This can be thought of as a list of MIDI events.
  115.  *
  116.  * The data types used to store the track is similar to how events are
  117.  * stored on a MIDI file, but used in a way that allows for faster parses.
  118.  * 
  119.  * This class is used on MidiPlayer::loadSong() to load the song and
  120.  * later play it with MidiPlayer::play().
  121.  *
  122.  * @short Stores a MIDI track with a simple API
  123.  * @version 0.9.5 17/01/2000
  124.  * @author Antonio Larrosa Jimenez <larrosa@kde.org>
  125.  */
  126. class MidiTrack
  127. {
  128.   private:
  129.     class MidiTrackPrivate;
  130.     MidiTrackPrivate *d;
  131.  
  132.     int    id;
  133.  
  134.     ulong size;
  135.     uchar *data;
  136.     uchar *ptrdata;
  137.  
  138.     bool  note[16][128]; // Notes that are set on or off by this track
  139.     ulong current_ticks; // Total number of ticks since beginning of song
  140.     ulong delta_ticks;   // Delta ticks from previous event to next event
  141.     ulong wait_ticks;    // Wait ticks from previous event in other track
  142.     // to next event in this track
  143.  
  144.     ulong currentpos; // Some songs don't have a endoftrack event, so
  145.     // we have to see when currentpos > size
  146.     int    endoftrack;
  147.  
  148.     ulong readVariableLengthValue(void);
  149.  
  150.     uchar lastcommand;  // This is to run light without overbyte :-)
  151.  
  152.  
  153.     double current_time; // in ms.
  154.     double time_at_previous_tempochange;  // in ms.
  155.     double ticks_from_previous_tempochange; // in ticks    
  156.     //    double    time_to_next_event;  // in ms.
  157.     double    time_at_next_event;  // in ms.
  158.     int    tPCN;
  159.     ulong    tempo;
  160.  
  161.     int    power2to(int i);
  162.  
  163.   public:
  164.     /**
  165.      * Constructor. 
  166.      * @param file the file to read the track from. It should be ready at the
  167.      * start of a track. MidiTrack reads just that track and the file is left at
  168.      * the end of this track).
  169.      * @param tpcn the ticks per cuarter note used in this file.
  170.      * @param Id the ID for this track.
  171.      */ 
  172.     MidiTrack(FILE *file,int tpcn,int Id);
  173.  
  174.     /**
  175.      * Destructor
  176.      */
  177.     ~MidiTrack();
  178.  
  179.     /**
  180.      * Makes the iterator advance the given number of ticks.
  181.      *
  182.      * @return 0 if OK, and 1 if you didn't handle this track well and you
  183.      * forgot to take an event (thing that will never happen if you use
  184.      * MidiPlayer::play() ).
  185.      */ 
  186.     int    ticksPassed (ulong ticks); 
  187.  
  188.     /**
  189.      * Makes the iterator advance the given number of milliseconds.
  190.      *
  191.      * @return 0 if OK, and 1 if you didn't handle this track well and you
  192.      * forgot to take an event (thing that will never happen if you use
  193.      * MidiPlayer::play() ).
  194.      */
  195.     int    msPassed    (ulong ms);
  196.  
  197.     /**
  198.      * Returns the current millisecond which the iterator is at.
  199.      */
  200.     int    currentMs   (double ms);
  201.  
  202.     /**
  203.      * Returns the number of ticks left for the next event.
  204.      */
  205.     ulong    waitTicks   (void) { return wait_ticks; }
  206.  
  207.     //    ulong   waitMs (void) {return time_to_next_event;};
  208.  
  209.     /**
  210.      * Returns the absolute number of milliseconds of the next event.
  211.      */ 
  212.     double   absMsOfNextEvent (void) { return time_at_next_event; }
  213.  
  214.     /**
  215.      * Change the tempo of the song.
  216.      */
  217.     void     changeTempo(ulong t);
  218.  
  219.     /**
  220.      * Reads the event at the iterator position, and puts it on the structure
  221.      * pointed to by @p ev.
  222.      */
  223.     void    readEvent(MidiEvent *ev);
  224.  
  225.     /**
  226.      * Initializes the iterator.
  227.      */
  228.     void    init(void);
  229.  
  230.     /**
  231.      * Clears the internal variables.
  232.      */
  233.     void    clear(void);
  234.  
  235. };
  236.  
  237. #endif
  238.